Skip to content

fix(mcp): reduce describe_source timeouts by using rollup tables for map key discovery - #2426

Merged
kodiakhq[bot] merged 4 commits into
mainfrom
claude/fix-describe-source-timeout
Jun 8, 2026
Merged

kodiakhq[bot] merged 4 commits into
mainfrom
claude/fix-describe-source-timeout

Conversation

@brandon-pereira

@brandon-pereira brandon-pereira commented Jun 8, 2026 •

Copy link
Copy Markdown
Member

Summary

clickstack_describe_source can time out (10s wall-clock limit) when discovering map attribute keys on large tables. Stage 2 (map key discovery) was always falling back to a full main-table scan—up to 3M rows per Map column—even when rollup tables were available, because metadataMVs and dateRange weren't computed yet at that point in the pipeline.

This hoists the rollup config and date range above Stage 2 so getMapKeys can use the fast rollup path. On the traces table in large environments this reduces Stage 2 from ~5-10s to <1s, keeping the full describe call well within the 10s budget.

Additionally, getMapValues now accepts an AbortSignal so that any per-key fallback queries are cancelled when the timeout fires, rather than running to completion against ClickHouse after the caller has already given up.

…map key discovery

Pass metadataMVs and dateRange to getMapKeys in Stage 2 so it queries
the rollup table instead of scanning millions of rows in the main table.

Also thread AbortSignal through getMapValues so fallback queries cancel
when the 10s wall-clock timeout fires.
@changeset-bot

changeset-bot Bot commented Jun 8, 2026 •

Copy link
Copy Markdown

🦋 Changeset detected

Latest commit: b4d6f7a

The changes in this PR will be included in the next version bump.

This PR includes changesets to release 3 packages
Name Type
@hyperdx/api Patch
@hyperdx/app Patch
@hyperdx/otel-collector Patch

Not sure what this means? Click here to learn what changesets are.

Click here if you're a maintainer who wants to add another changeset to this PR

@vercel

vercel Bot commented Jun 8, 2026 •

Copy link
Copy Markdown

The latest updates on your projects. Learn more about Vercel for GitHub.

Project Deployment Actions Updated (UTC)
hyperdx-oss Ready Ready Preview, Comment Jun 8, 2026 7:37pm
hyperdx-storybook Ready Ready Preview, Comment Jun 8, 2026 7:37pm

Request Review

@github-actions github-actions Bot added the review/tier-3 Standard — full human review required label Jun 8, 2026
@github-actions

github-actions Bot commented Jun 8, 2026 •

Copy link
Copy Markdown
Contributor

🟡 Tier 3 — Standard

Introduces new logic, modifies core functionality, or touches areas with non-trivial risk.

Why this tier:

  • Cross-layer change: touches backend (packages/api) + shared utils (packages/common-utils)

Review process: Full human review — logic, architecture, edge cases.
SLA: First-pass feedback within 1 business day.

Stats
  • Production files changed: 2
  • Production lines changed: 36
  • Branch: claude/fix-describe-source-timeout
  • Author: brandon-pereira

To override this classification, remove the review/tier-3 label and apply a different review/tier-* label. Manual overrides are preserved on subsequent pushes.

@github-actions

github-actions Bot commented Jun 8, 2026 •

Copy link
Copy Markdown
Contributor

E2E Test Results

✅ All tests passed • 197 passed • 3 skipped • 1353s

Status Count
✅ Passed 197
❌ Failed 0
⚠️ Flaky 5
⏭️ Skipped 3

Tests ran across 4 shards in parallel.

View full report →

@greptile-apps

greptile-apps Bot commented Jun 8, 2026 •

Copy link
Copy Markdown
Contributor

Greptile Summary

This PR fixes clickstack_describe_source timeouts by hoisting metadataMVs and dateRange above Stage 2 so getMapKeys can use the fast rollup-table path for map attribute key discovery instead of always falling back to a full main-table scan. It also threads AbortSignal into getMapKeys and the per-key fallback queries in getMapValues so in-flight ClickHouse queries are cancelled when the 10s timeout fires.

  • Rollup path enabled for Stage 2: metadataMVs and dateRange are now computed once before Stage 1 and passed down to getMapKeys in Stage 2, giving the rollup branch the data it needs to skip expensive main-table scans.
  • Signal propagation: AbortSignal is wired into both the rollup ClickHouse query and the main-table fallback query inside getMapKeys, and into the per-key getMapValues calls in getAllKeyValues, so the ClickHouse server stops executing these queries as soon as the caller times out.

Confidence Score: 4/5

Safe to merge for the common case, but a timeout during the newly-enabled rollup query in Stage 2 will cache an empty key list for the entire aligned time window, causing all subsequent describe calls to silently return no map attribute keys until the process restarts.

The rollup-path closure in getMapKeys catches all errors — including the AbortError raised when signal fires — and returns []. getOrFetch stores this empty array in the process-level MetadataCache. Because the cache check runs before the rollup branch, every follow-on call for the same source/column/time-window hits the early-return and gets [], bypassing both the rollup and the main-table fallback. Before this PR, Stage 2 never reached the rollup path, so this latent behaviour was harmless; the new wiring makes it reachable for the first time.

The rollup try/catch block in packages/common-utils/src/core/metadata.ts (getMapKeys, ~line 428) needs attention — it should distinguish abort errors from genuine query failures before returning [].

Important Files Changed

Filename Overview
packages/api/src/mcp/tools/sources/describeSource.ts Hoists metadataMVs and dateRange above Stage 2 and wires signal into getMapKeys, enabling the fast rollup path for map-key discovery; the structural change is clean, but the rollup path abort-error-swallowing behaviour can now poison the persistent cache when a timeout fires during Stage 2.
packages/common-utils/src/core/metadata.ts Adds signal to getMapKeys (both rollup and main-table paths) and getMapValues (fallback per-key queries); the rollup closure's try/catch still catches AbortError and returns [], which getOrFetch caches, poisoning the module-level cache for that time window.
.changeset/fix-describe-source-timeout.md Standard changeset entry marking a patch bump for @hyperdx/api; no logic changes.

Sequence Diagram

sequenceDiagram
    participant C as MCP Caller
    participant DS as describeSource
    participant GK as getMapKeys
    participant RU as Rollup Table
    participant MT as Main Table

    C->>DS: clickstack_describe_source
    DS->>DS: compute metadataMVs + dateRange (hoisted above Stage 2)
    DS->>DS: Stage 1 - getColumns()
    DS->>GK: getMapKeys with metadataMVs + dateRange + signal
    note over GK: Check persistent MetadataCache
    alt rollup path available
        GK->>RU: SELECT Key FROM keyRollupTable WHERE ColumnIdentifier AND Timestamp range
        RU-->>GK: keys
        GK-->>DS: keys
    else rollup empty or unavailable
        GK->>MT: full table scan
        MT-->>GK: keys
        GK-->>DS: keys
    end
    DS->>DS: Stage 3 - getAllKeyValues LC columns
    DS->>DS: Stage 4 - getAllKeyValues map attribute values
    DS-->>C: schema + mapAttributeKeys + values
Loading

Reviews (3): Last reviewed commit: "Merge branch 'main' into claude/fix-desc..." | Re-trigger Greptile

@kodiakhq
kodiakhq Bot merged commit cdd7ca0 into main Jun 8, 2026
19 checks passed
@kodiakhq
kodiakhq Bot deleted the claude/fix-describe-source-timeout branch June 8, 2026 19:43

This branch was successfully deployed

2 active deployments
Preview – hyperdx-oss — b4d6f7a6 Deployed Jun 8, 2026 by vercel[bot]
Preview – hyperdx-storybook — b4d6f7a6 Deployed Jun 8, 2026 by vercel[bot]
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

automerge review/tier-3 Standard — full human review required

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants